package studio.raptor.dispatcher.server.dao;

import javax.sql.DataSource;

import com.sun.org.apache.xpath.internal.SourceTree;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Repository;
import studio.raptor.dispatcher.common.constant.TopicConst;
import studio.raptor.dispatcher.server.entity.BaseSubscriptionConfig;
import studio.raptor.dispatcher.server.entity.SubItem;
import studio.raptor.hub.common.util.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.*;

/**
 * 加载分发器配置dao类
 *
 * @author jack
 * @since 1.0
 */
@Repository
public class DispatcherConfigDAO {
    private static final Logger log = LoggerFactory.getLogger(DispatcherConfigDAO.class);

    @Autowired
    @Qualifier("dispatcherDataSource")
    DataSource dataSource;

    public Set<String> queryItemNames(){
        String sql = "SELECT t.item_name FROM sub_base_item t";
        Connection connection = null;
        PreparedStatement pstmt = null;
        Set<String> itemNames = new HashSet<String>();

        try {
            connection = dataSource.getConnection();
            pstmt = connection.prepareStatement(sql);

            ResultSet resultSet = pstmt.executeQuery();
            while (resultSet.next()) {
                String itemName = resultSet.getString("ITEM_NAME");
                //去除"_"
                itemName = itemName.replace("_","");
                itemName = itemName.toUpperCase();
                itemNames.add(itemName);
            }
        } catch (Exception e) {
            log.error("query itemNames failed", e);
        } finally {
            JdbcUtils.close(pstmt);
            JdbcUtils.close(connection);
        }

        return itemNames;
    }

    /**
     * 查询配置id集合
     *
     * @param topic nrm or sar
     * @return
     */
    public List<String> queryConfigIdsByTopic(String topic) {
        String sql = "SELECT DISTINCT t3.config_id FROM sub_relation t1,sub_channel t2,sub_config t3 WHERE t1.channel_id = t2.channel_id AND t1.config_id = t3.config_id  AND t2.type = ?";
        Connection connection = null;
        PreparedStatement pstmt = null;
        List<String> configIds = new ArrayList<String>();

        try {
            connection = dataSource.getConnection();
            pstmt = connection.prepareStatement(sql);
            pstmt.setInt(1, TopicConst.SAR_TOPIC.equals(topic) ? 1 : 2);//1：停复机、2:：普通业务

            ResultSet resultSet = pstmt.executeQuery();
            while (resultSet.next()) {
                String configId = resultSet.getString("config_id");
                configIds.add(configId);
            }
        } catch (Exception e) {
            log.error("query subscription base config by topic failed", e);
        } finally {
            JdbcUtils.close(pstmt);
            JdbcUtils.close(connection);
        }

        return configIds;
    }

    /**
     * 查询常规维度的订阅关系配置
     *
     * @param topic sar or nrm
     * @return
     */
    public List queryBaseSubConfigByTopic(String topic) {
        String sql = "SELECT t3.item_name AS item_name,t2.item_value,t4.code,t4.name,t2.item_action,t2.config_id,t1.is_send " +
                "from sub_relation t1,sub_config t2,sub_base_item t3,sub_channel t4 WHERE t1.channel_id = t4.channel_id " +
                "and t1.config_id = t2.config_id and t2.item_id = t3.item_id and t4.type = ? and t1.config_id = ?";
        Connection connection = null;
        PreparedStatement pstmt = null;
        List<BaseSubscriptionConfig> baseSubscriptionConfigs = new ArrayList<BaseSubscriptionConfig>();
        List<String> configIds = queryConfigIdsByTopic(topic);
        ;

        try {
            connection = dataSource.getConnection();
            pstmt = connection.prepareStatement(sql);

            pstmt.setInt(1, TopicConst.SAR_TOPIC.equals(topic) ? 1 : 2);//1：停复机、2:：普通业务

            for (String configId : configIds) {
                pstmt.setString(2, configId);

                Set<SubItem> subItems = new HashSet<SubItem>();
                ResultSet resultSet = pstmt.executeQuery();
                String code = null;
                String name = null;
                Integer isSend = null;
                String areaId = null;
                while (resultSet.next()) {
                    code = resultSet.getString("code");
                    name = resultSet.getString("name");
                    String itemName = resultSet.getString("item_name");
                    String itemValue = resultSet.getString("item_value");
                    String itemAction = resultSet.getString("item_action");
                    SubItem subItem = new SubItem(itemName, itemValue,itemAction);
                    subItems.add(subItem);
                    isSend = resultSet.getInt("is_send");
                }
                BaseSubscriptionConfig baseSubscriptionConfig = buildBaseSubConfig(code + "-" + name, configId, subItems,isSend,areaId);
                baseSubscriptionConfigs.add(baseSubscriptionConfig);
            }
        } catch (Exception e) {
            log.error("query subscription base config by topic failed", e);
        } finally {
            JdbcUtils.close(pstmt);
            JdbcUtils.close(connection);
        }

        return baseSubscriptionConfigs;

    }

    /**
     * 查询其他维度的订阅关系配置
     *
     * @param topic sar or nrm
     * @return
     */
    public Map<String, String> queryOtherSubConfigByTopic(String topic) {
        String sql = "SELECT * FROM sub_channel t WHERE t.type = ? AND t.handleclass IS NOT NULL";
        Connection connection = null;
        PreparedStatement pstmt = null;
        Map<String/*code+name*/, String/*handleClass*/> handleClassMap = new HashMap<String, String>();

        try {
            connection = dataSource.getConnection();
            pstmt = connection.prepareStatement(sql);
            pstmt.setInt(1, TopicConst.SAR_TOPIC.equals(topic) ? 1 : 2);//1：停复机、2:：普通业务

            ResultSet resultSet = pstmt.executeQuery();
            while (resultSet.next()) {
                String code = resultSet.getString("code");
                String name = resultSet.getString("name");
                String handleClass = resultSet.getString("handleClass");
                handleClassMap.put(code + "-" + name, handleClass);
            }
        } catch (Exception e) {
            log.error("query subscription other config by topic failed", e);

        } finally {
            JdbcUtils.close(pstmt);
            JdbcUtils.close(connection);
        }

        return handleClassMap;
    }

    /**
     * @param codeName channelCode - channelName
     * @param configId 配置id
     * @param subItems 配置项集合
     * @return
     */
    private BaseSubscriptionConfig buildBaseSubConfig(String codeName, String configId, Set<SubItem> subItems,Integer isSend,String areaId) {
        BaseSubscriptionConfig baseSubscriptionConfig = new BaseSubscriptionConfig();
        baseSubscriptionConfig.setItemSet(subItems);
        baseSubscriptionConfig.setCodeName(codeName);
        baseSubscriptionConfig.setConfigId(configId);
        baseSubscriptionConfig.setIsSend(isSend);
        baseSubscriptionConfig.setAreaId(areaId);
        return baseSubscriptionConfig;
    }
}
